/*
* Sun Public License Notice
*
* The contents of this file are subject to the Sun Public License
* Version 1.0 (the "License"). You may not use this file except in
* compliance with the License. A copy of the License is available at
* http://www.sun.com/
*
* The Original Code is Forte for Java, Community Edition. The Initial
* Developer of the Original Code is Sun Microsystems, Inc. Portions
* Copyright 1997-2000 Sun Microsystems, Inc. All Rights Reserved.
*/
package org.netbeans.updater;
import java.io.*;
import java.util.Enumeration;
import java.util.jar.*;
import java.util.ResourceBundle;
import org.openide.util.NbBundle;
/** Class used by autoupdate module for the work with module files and
* for installing / uninstalling modules
*
* @author Petr Hrebejk
* @version
*/
public class ModuleUpdater extends Thread {
ResourceBundle bundle = java.util.ResourceBundle.getBundle("org/netbeans/updater/Bundle"); // NOI18N
/** Platform dependent file name separator */
private static final String FILE_SEPARATOR = System.getProperty ("file.separator");
/** Relative name of directory where the .NBM files are downloaded */
private static final String DOWNLOAD_DIR = "update" + FILE_SEPARATOR + "download"; // NOI18N
/** Relative name of backup directory */
private static final String BACKUP_DIR = "update" + FILE_SEPARATOR + "backup"; // NOI18N
/** Relative name of netbeans/lib directory */
private static final String NB_LIB_DIR = "lib"; // NOI18N
/** Name of extension directory */
private static final String EXT_DIR = "ext"; // NOI18N
/** Relative name of java/lib/ext directory */
private static final String JAVA_LIB_EXT_DIR = "lib" + FILE_SEPARATOR + EXT_DIR; // NOI18N
/** The name of zip entry containing netbeans files */
public static final String UPDATE_NETBEANS_DIR = "netbeans"; // NOI18N
/** The name of zip entry containing java_extension files */
public static final String UPDATE_JAVA_EXT_DIR = "java_ext"; // NOI18N
/** Extension of the distribution files */
private static final String NBM_EXTENSION = "nbm"; // NOI18N
private static File downloadDirectory = null;
private static File backupDirectory = null;
private static File netbeansDirectory = null;
private static File nbLibDirectory = null;
private static File javaLibExtDirectory = null;
/** All distribution files in the download directory */
private File[] nbmFiles = null;
/** Should the thread stop */
private volatile boolean stop = false;
private volatile boolean suspend = false;
/** Total length of unpacked files */
private long totalLength;
/** Creates new ModuleUpdater */
public void run() {
getDownloadDirectory();
checkStop();
if ( downloadDirectory == null ) {
endRun();
}
checkStop();
nbmFiles = getNBMFiles();
if ( nbmFiles == null || nbmFiles.length == 0 ) {
endRun();
}
checkStop();
totalLength();
checkStop();
unpack();
UpdaterFrame.unpackingFinished();
}
/** ends the run of update */
void endRun() {
stop = true;
}
/** checks wheter ends the run of update */
private void checkStop() {
if ( suspend )
while ( suspend );
if ( stop ) {
System.exit( 0 );
}
}
/** Creates array of all .NBM files in the update/download directory
*/
static File[] getNBMFiles() {
File dirList[] = downloadDirectory.listFiles( new FilenameFilter() {
public boolean accept( File dir, String name ) {
return name.endsWith( NBM_EXTENSION );
}
});
return dirList;
}
/** Determines size of unpacked modules */
private void totalLength() {
totalLength = 0L;
UpdaterFrame.setLabel( bundle.getString( "CTL_PreparingUnpack" ) );
UpdaterFrame.setProgressRange( 0, nbmFiles.length );
for( int i = 0; i < nbmFiles.length; i++ ) {
JarFile jarFile = null;
try {
UpdaterFrame.setProgressValue( i + 1 );
jarFile = new JarFile( nbmFiles[i] );
Enumeration entries = jarFile.entries();
while( entries.hasMoreElements() ) {
JarEntry entry = (JarEntry) entries.nextElement();
checkStop();
if ( ( entry.getName().startsWith( UPDATE_NETBEANS_DIR ) ||
entry.getName().startsWith( ModuleUpdater.UPDATE_JAVA_EXT_DIR ) ) &&
!entry.isDirectory() ) {
totalLength += entry.getSize();
}
}
}
catch ( java.io.IOException e ) {
// Ignore non readable files
}
finally {
try {
if ( jarFile != null )
jarFile.close();
}
catch ( java.io.IOException e ) {
// We can't close the file do nothing
// System.out.println( "Cant close : " + e ); // NOI18N
}
}
}
}
/** Unpack the distribution files into update directory */
void unpack () {
long bytesRead = 0L;
// System.out.println("Total lengtg " + totalLength ); // NOI18N
UpdaterFrame.setLabel( "" ); // NOI18N
UpdaterFrame.setProgressRange( 0, totalLength );
for( int i = 0; i < nbmFiles.length; i++ ) {
UpdaterFrame.setLabel( bundle.getString("CTL_UnpackingFile") + " " + nbmFiles[i].getName() ); //NOI18N
UpdaterFrame.setProgressValue( bytesRead );
JarFile jarFile = null;
try {
jarFile = new JarFile( nbmFiles[i] );
Enumeration entries = jarFile.entries();
while( entries.hasMoreElements() ) {
JarEntry entry = (JarEntry) entries.nextElement();
checkStop();
if ( entry.getName().startsWith( UPDATE_NETBEANS_DIR ) ) {
// Copy files into netbeans directory
if ( entry.isDirectory() ) {
File newDir = new File( getNetbeansDirectory(), entry.getName().substring( UPDATE_NETBEANS_DIR.length() ) );
if ( !newDir.isDirectory() )
newDir.mkdirs();
File newBckDir = new File( getBackupDirectory(), entry.getName() );
if ( !newBckDir.isDirectory() )
newBckDir.mkdirs();
}
else {
File destFile = new File( getNetbeansDirectory(), entry.getName().substring( UPDATE_NETBEANS_DIR.length() ) );
if ( destFile.exists() ) {
File bckFile = new File( getBackupDirectory(), entry.getName() );
// System.out.println("Backing up" ); // NOI18N
copyStreams( new FileInputStream( destFile ), new FileOutputStream( bckFile ) );
}
copyStreams( jarFile.getInputStream( entry ), new FileOutputStream( destFile ) );
bytesRead += entry.getSize();
UpdaterFrame.setProgressValue( bytesRead );
}
}
else if ( entry.getName().startsWith( ModuleUpdater.UPDATE_JAVA_EXT_DIR ) &&
!entry.isDirectory() ) {
// Copy files into java/lib/ext directory
File destFile = new File( getJavaLibExtDirectory(), entry.getName().substring( UPDATE_JAVA_EXT_DIR.length() ) );
if ( destFile.exists() ) {
File bckFile = new File( getBackupDirectory(), ModuleUpdater.UPDATE_JAVA_EXT_DIR + FILE_SEPARATOR + entry.getName().substring( UPDATE_NETBEANS_DIR.length() ) );
copyStreams( new FileInputStream( destFile ), new FileOutputStream( bckFile ) );
}
copyStreams( jarFile.getInputStream( entry ), new FileOutputStream( destFile ) );
bytesRead += entry.getSize();
UpdaterFrame.setProgressValue( bytesRead );
}
}
}
catch ( java.io.IOException e ) {
// Ignore non readable files
}
finally {
try {
if ( jarFile != null )
jarFile.close();
}
catch ( java.io.IOException e ) {
// We can't close the file do nothing
// System.out.println("Can't close : " + e ); // NOI18N
}
//System.out.println("Dleting :" + nbmFiles[i].getName() + ":" + nbmFiles[i].delete() ); // NOI18N
nbmFiles[i].delete();
//nbmFiles[i].deleteOnExit();
}
}
}
/** The directory where to download the distribution files of modules */
public static File getDownloadDirectory() {
if ( downloadDirectory == null ) {
if ( isMultiuser() )
downloadDirectory = new File (System.getProperty ("netbeans.user") + FILE_SEPARATOR + DOWNLOAD_DIR );
else
downloadDirectory = new File (System.getProperty ("netbeans.home") + FILE_SEPARATOR + DOWNLOAD_DIR );
if ( !downloadDirectory.isDirectory() )
downloadDirectory.mkdirs();
}
return downloadDirectory;
}
/** The directory where to backup old versions of modules */
public static File getBackupDirectory() {
if ( backupDirectory == null ) {
if ( isMultiuser() )
backupDirectory = new File (System.getProperty ("netbeans.user") + FILE_SEPARATOR + BACKUP_DIR );
else
backupDirectory = new File (System.getProperty ("netbeans.home") + FILE_SEPARATOR + BACKUP_DIR );
if ( !backupDirectory.isDirectory() )
backupDirectory.mkdirs();
}
return backupDirectory;
}
/** Gets the netbeans directory */
public static File getNetbeansDirectory() {
if ( netbeansDirectory == null ) {
if ( isMultiuser() )
netbeansDirectory = new File (System.getProperty ("netbeans.user") );
else
netbeansDirectory = new File (System.getProperty ("netbeans.home") );
}
return netbeansDirectory;
}
/** The directory of libraries that are added to CLASSPATH on startup */
public static File getNbLibDirectory() {
if ( nbLibDirectory == null ) {
if ( isMultiuser() )
nbLibDirectory = new File (System.getProperty ("netbeans.user") + FILE_SEPARATOR + NB_LIB_DIR );
else
nbLibDirectory = new File (System.getProperty ("netbeans.home") + FILE_SEPARATOR + NB_LIB_DIR );
}
File nbLibExt = new File( nbLibDirectory, EXT_DIR );
if ( !nbLibExt.isDirectory() )
nbLibExt.mkdirs();
return nbLibDirectory;
}
/** The directory lib/ext directory of JDK */
public static File getJavaLibExtDirectory() {
if ( javaLibExtDirectory == null ) {
javaLibExtDirectory = new File (System.getProperty ("java.home") + FILE_SEPARATOR + JAVA_LIB_EXT_DIR );
}
if ( canWrite( javaLibExtDirectory, true ) )
return javaLibExtDirectory;
else
return getNbLibDirectory();
}
private static boolean isMultiuser() {
if ( System.getProperty ("netbeans.user") == null ||
System.getProperty ("netbeans.home").equals( System.getProperty ("netbeans.user") ) )
return false;
else
return true;
}
/*
private static Manifest getManifest( File file ) throws java.io.IOException {
JarFile jar = new JarFile( file );
Manifest man = jar.getManifest();
jar.close();
return man;
}
*/
/** Copies two streams */
private void copyStreams( InputStream src, OutputStream dest ) throws java.io.IOException {
BufferedInputStream bsrc = new BufferedInputStream( src );
BufferedOutputStream bdest = new BufferedOutputStream( dest );
int count = 0;
int c;
try {
while( ( c = bsrc.read() ) != -1 ) {
bdest.write( c );
count++;
if ( count > 8500 ) {
count = 0;
checkStop();
}
}
}
finally {
bsrc.close();
bdest.close();
}
}
/** Test whether the user has rights to write into directory */
private static boolean canWrite( File dir, boolean create ) {
if ( !dir.exists() && create )
dir.mkdirs();
if ( !dir.isDirectory() || !dir.canWrite() )
return false;
File tmp = null;
try {
tmp = File.createTempFile( "test", "access", dir ); // NOI18N
}
catch ( java.io.IOException e ) {
return false;
}
if ( tmp == null )
return false;
boolean cw = tmp.canWrite();
if (cw)
tmp.delete();
return cw;
}
/*
void cancel() {
suspend = true;
StopWarning stopWarning = new StopWarning();
stopWarning.show();
stop = stopWarning.isStop();
suspend = false;
}
*/
}
/*
* Log
* 9 Gandalf 1.8 1/24/00 Petr Hrebejk Space in unpacking files
* label adde
* 8 Gandalf 1.7 1/13/00 Petr Hrebejk i18n mk2
* 7 Gandalf 1.6 1/13/00 Petr Hrebejk i18n
* 6 Gandalf 1.5 1/10/00 Petr Hrebejk Multiuser bug fixed
* 5 Gandalf 1.4 1/9/00 Petr Hrebejk Multiuser recognition
* changed
* 4 Gandalf 1.3 10/23/99 Ian Formanek NO SEMANTIC CHANGE - Sun
* Microsystems Copyright in File Comment
* 3 Gandalf 1.2 10/12/99 Petr Hrebejk Backs up the replaced
* files
* 2 Gandalf 1.1 10/7/99 Petr Hrebejk
* 1 Gandalf 1.0 10/6/99 Petr Hrebejk
* $
*/